<!DOCTYPE html>
<html lang="zh-CN">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>音乐旋律波长可视化</title>
    <style>
        * {
            margin: 0;
            padding: 0;
            box-sizing: border-box;
        }
        
        body {
            display: flex;
            flex-direction: column;
            justify-content: center;
            align-items: center;
            min-height: 100vh;
            background: linear-gradient(135deg, #1a1a2e 0%, #16213e 100%);
            font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif;
            color: #fff;
            padding: 20px;
            overflow-x: hidden;
        }
        
        .container {
            width: 100%;
            max-width: 1000px;
            text-align: center;
        }
        
        h1 {
            font-size: 2.8rem;
            margin-bottom: 10px;
            background: linear-gradient(90deg, #ff6b6b, #ffa36c, #ffde7d, #a3de83, #6a98f0, #a594f9);
            -webkit-background-clip: text;
            background-clip: text;
            color: transparent;
            text-shadow: 0 0 20px rgba(255, 255, 255, 0.2);
        }
        
        .subtitle {
            font-size: 1.2rem;
            color: #a0a0c0;
            margin-bottom: 40px;
        }
        
        .visualizer-container {
            position: relative;
            width: 100%;
            height: 300px;
            margin: 40px 0;
            display: flex;
            justify-content: center;
            align-items: center;
            overflow: hidden;
            border-radius: 20px;
            background: rgba(0, 0, 0, 0.3);
            box-shadow: 0 10px 30px rgba(0, 0, 0, 0.4);
        }
        
        .bars-container {
            display: flex;
            justify-content: center;
            align-items: flex-end;
            height: 200px;
            width: 90%;
            gap: 4px;
        }
        
        .bar {
            width: 12px;
            background: linear-gradient(to top, #ff6b6b, #ffde7d, #6a98f0);
            border-radius: 6px 6px 0 0;
            transition: height 0.1s ease-out;
            box-shadow: 0 0 10px rgba(106, 152, 240, 0.5);
        }
        
        .controls {
            display: flex;
            justify-content: center;
            gap: 20px;
            margin: 30px 0;
            flex-wrap: wrap;
        }
        
        button {
            padding: 12px 25px;
            border: none;
            border-radius: 50px;
            background: linear-gradient(90deg, #6a98f0, #a594f9);
            color: white;
            font-size: 1rem;
            font-weight: bold;
            cursor: pointer;
            transition: all 0.3s ease;
            box-shadow: 0 5px 15px rgba(106, 152, 240, 0.4);
        }
        
        button:hover {
            transform: translateY(-3px);
            box-shadow: 0 8px 20px rgba(106, 152, 240, 0.6);
        }
        
        button:active {
            transform: translateY(1px);
        }
        
        button:disabled {
            background: #555;
            cursor: not-allowed;
            transform: none;
            box-shadow: none;
        }
        
        .file-input {
            display: none;
        }
        
        .file-label {
            padding: 12px 25px;
            border-radius: 50px;
            background: linear-gradient(90deg, #ff6b6b, #ffa36c);
            color: white;
            font-size: 1rem;
            font-weight: bold;
            cursor: pointer;
            transition: all 0.3s ease;
            box-shadow: 0 5px 15px rgba(255, 107, 107, 0.4);
        }
        
        .file-label:hover {
            transform: translateY(-3px);
            box-shadow: 0 8px 20px rgba(255, 107, 107, 0.6);
        }
        
        .audio-info {
            margin: 0 auto;
            margin-top: 20px;
            padding: 15px;
            background: rgba(255, 255, 255, 0.1);
            border-radius: 15px;
            width: 100%;
            max-width: 500px;
        }
        
        .track-info {
            font-size: 1.1rem;
            margin-bottom: 10px;
        }
        
        .frequency-info {
            display: flex;
            justify-content: space-around;
            margin-top: 15px;
            font-size: 0.9rem;
            color: #a0a0c0;
        }
        
        @keyframes wave-animation {
            0% {
                transform: translateX(0);
            }
            100% {
                transform: translateX(-50%);
            }
        }
        
        @keyframes pulse {
            0% {
                box-shadow: 0 0 0 0 rgba(106, 152, 240, 0.7);
            }
            70% {
                box-shadow: 0 0 0 15px rgba(106, 152, 240, 0);
            }
            100% {
                box-shadow: 0 0 0 0 rgba(106, 152, 240, 0);
            }
        }
        
        .pulse {
            animation: pulse 2s infinite;
        }
        
        @media (max-width: 768px) {
            h1 {
                font-size: 2rem;
            }
            
            .subtitle {
                font-size: 1rem;
            }
            
            .visualizer-container {
                height: 250px;
            }
            
            .bars-container {
                width: 95%;
            }
            
            .bar {
                width: 8px;
            }
            
            .controls {
                flex-direction: column;
                align-items: center;
            }
            
            button, .file-label {
                width: 80%;
            }
        }
    </style>
</head>
<body>
    <div class="container">
        <h1>音乐旋律波长可视化</h1>
        <p class="subtitle">体验音乐频率与节奏的动态视觉表现</p>
        
        <div class="visualizer-container">
            <div class="bars-container" id="barsContainer">
                <!-- 音频条将通过JavaScript动态生成 -->
            </div>
        </div>
        
        <div class="controls">
            <button id="startBtn" class="pulse">开始可视化</button>
            <input type="file" id="audioFile" class="file-input" accept="audio/*">
            <label for="audioFile" class="file-label">选择音频文件</label>
            <button id="stopBtn">停止</button>
        </div>
        
        <div class="audio-info">
            <div class="track-info" id="trackInfo">未选择音频文件</div>
            <div class="frequency-info">
                <div>低频: <span id="lowFreq">0</span> Hz</div>
                <div>中频: <span id="midFreq">0</span> Hz</div>
                <div>高频: <span id="highFreq">0</span> Hz</div>
            </div>
        </div>
    </div>

    <script>
        document.addEventListener('DOMContentLoaded', function() {
            // 获取DOM元素
            const barsContainer = document.getElementById('barsContainer');
            const startBtn = document.getElementById('startBtn');
            const stopBtn = document.getElementById('stopBtn');
            const audioFile = document.getElementById('audioFile');
            const trackInfo = document.getElementById('trackInfo');
            const lowFreq = document.getElementById('lowFreq');
            const midFreq = document.getElementById('midFreq');
            const highFreq = document.getElementById('highFreq');
            
            // 创建音频上下文和分析器
            let audioContext;
            let analyser;
            let source;
            let dataArray;
            let bufferLength;
            let isPlaying = false;
            
            // 创建音频条
            const barCount = 64;
            for (let i = 0; i < barCount; i++) {
                const bar = document.createElement('div');
                bar.className = 'bar';
                bar.style.height = '5px';
                barsContainer.appendChild(bar);
            }
            const bars = document.querySelectorAll('.bar');
            
            // 初始化音频上下文
            function initAudioContext() {
                if (!audioContext) {
                    audioContext = new (window.AudioContext || window.webkitAudioContext)();
                    analyser = audioContext.createAnalyser();
                    analyser.fftSize = 256;
                    bufferLength = analyser.frequencyBinCount;
                    dataArray = new Uint8Array(bufferLength);
                }
            }
            
            // 开始可视化
            startBtn.addEventListener('click', function() {
                if (!isPlaying) {
                    // 如果没有选择文件，使用默认音频
                    if (!source) {
                        createOscillator();
                    }
                    
                    initAudioContext();
                    isPlaying = true;
                    startBtn.disabled = true;
                    stopBtn.disabled = false;
                    animate();
                }
            });
            
            // 停止可视化
            stopBtn.addEventListener('click', function() {
                if (isPlaying) {
                    isPlaying = false;
                    startBtn.disabled = false;
                    stopBtn.disabled = true;
                    
                    if (source && source.stop) {
                        source.stop();
                        source = null;
                    }
                    
                    // 重置音频条高度
                    bars.forEach(bar => {
                        bar.style.height = '5px';
                    });
                }
            });
            
            // 处理文件选择
            audioFile.addEventListener('change', function(e) {
                const file = e.target.files[0];
                if (file) {
                    const objectUrl = URL.createObjectURL(file);
                    playAudioFile(objectUrl);
                    trackInfo.textContent = `正在播放: ${file.name}`;
                }
            });
            
            // 播放音频文件
            function playAudioFile(url) {
                initAudioContext();
                
                // 停止当前播放的音频
                if (source && source.stop) {
                    source.stop();
                }
                
                // 创建新的音频源
                const audio = new Audio();
                audio.src = url;
                audio.crossOrigin = "anonymous";
                
                source = audioContext.createMediaElementSource(audio);
                source.connect(analyser);
                analyser.connect(audioContext.destination);
                
                audio.play();
                isPlaying = true;
                startBtn.disabled = true;
                stopBtn.disabled = false;
                animate();
            }
            
            // 创建默认振荡器（用于演示）
            function createOscillator() {
                initAudioContext();
                
                const oscillator = audioContext.createOscillator();
                oscillator.type = 'sawtooth';
                oscillator.frequency.setValueAtTime(220, audioContext.currentTime);
                
                const gainNode = audioContext.createGain();
                gainNode.gain.value = 0.1;
                
                oscillator.connect(gainNode);
                gainNode.connect(analyser);
                analyser.connect(audioContext.destination);
                
                oscillator.start();
                source = oscillator;
            }
            
            // 动画循环
            function animate() {
                if (!isPlaying) return;
                
                analyser.getByteFrequencyData(dataArray);
                
                // 更新音频条高度
                for (let i = 0; i < bars.length; i++) {
                    const value = dataArray[i];
                    const percent = value / 256;
                    const height = Math.max(percent * 200, 5);
                    bars[i].style.height = `${height}px`;
                    
                    // 根据频率值调整颜色
                    const hue = i * 360 / bars.length;
                    bars[i].style.background = `linear-gradient(to top, 
                        hsl(${hue}, 100%, 50%), 
                        hsl(${hue + 30}, 100%, 70%), 
                        hsl(${hue + 60}, 100%, 50%))`;
                }
                
                // 更新频率信息
                const lowFreqValue = Math.round(dataArray[2] * 2);
                const midFreqValue = Math.round(dataArray[8] * 4);
                const highFreqValue = Math.round(dataArray[20] * 8);
                
                lowFreq.textContent = lowFreqValue;
                midFreq.textContent = midFreqValue;
                highFreq.textContent = highFreqValue;
                
                requestAnimationFrame(animate);
            }
            
            // 初始化按钮状态
            stopBtn.disabled = true;
        });
    </script>
</body>
</html>